const connection = require('../../sql');

class ConfigService {
	// 获取单个参数值
	/* async getConfigValue(configKey) {
		const sql = `
		  SELECT config_value 
		  FROM sys_config 
		  WHERE config_key = ? 
		  LIMIT 1
		`;
		const [rows] = await connection.execute(sql, [configKey]);

		if (!rows.length) {
			throw new Error(`未找到参数配置: ${configKey}`);
		}

		return rows[0].config_value;
	} */
	async getConfigValue(configKey) {
		// 处理传入参数，确保为去重后的数组
		const keys = Array.isArray(configKey) ? [...new Set(configKey)] : [configKey];
		if (keys.length === 0) {
			throw new Error('至少需要提供一个配置键');
		}

		// 生成动态占位符防止SQL注入
		const placeholders = keys.map(() => '?').join(',');
		const sql = `
				SELECT config_key, config_value 
				FROM sys_config 
				WHERE config_key IN (${placeholders})
			`;

		// 执行参数化查询
		const [rows] = await connection.execute(sql, keys);

		// 校验是否存在缺失配置
		if (rows.length !== keys.length) {
			const foundKeys = new Set(rows.map((row) => row.config_key));
			const missingKeys = keys.filter((key) => !foundKeys.has(key));
			throw new Error(`未找到参数配置: ${missingKeys.join(', ')}`);
		}

		// 构建键值映射对象
		const configMap = rows.reduce((map, row) => {
			map[row.config_key] = row.config_value;
			return map;
		}, {});

		// 根据入参类型返回对应结构
		return Array.isArray(configKey) ? configMap : configMap[keys[0]];
	}
	async listConfigs({ configName, page, limit }) {
		const offset = (page - 1) * limit;
		let whereClause = '';
		const params = [];

		if (configName) {
			whereClause += 'WHERE config_name LIKE ?';
			params.push(`%${configName}%`);
		}

		const countSql = `
        SELECT COUNT(*) as total 
        FROM sys_config 
        ${whereClause}
      `;
		const listSql = `
        SELECT 
          id, 
          config_name AS configName, 
          config_key AS configKey, 
          config_value AS configValue, 
          is_lock AS isLock, 
          create_id AS createId, 
          create_time AS createTime, 
          update_id AS updateId, 
          update_time AS updateTime, 
          remark 
        FROM sys_config 
        ${whereClause}
        ORDER BY create_time ASC
        LIMIT ? OFFSET ?
      `;
		const [countResult] = await connection.execute(countSql, params);
		const [rows] = await connection.execute(listSql, [...params, String(limit), String(offset)]);

		return {
			current: page,
			limit,
			totalPage: Math.ceil(countResult[0].total / limit),
			total: countResult[0].total,
			rows,
		};
	}

	async saveConfig({ id, configName, configKey, configValue, remark, userId }) {
		try {
			if (id) {
				// 修改
				const updateSql = `
            UPDATE sys_config 
            SET config_name = ?, config_key = ?, config_value = ?, remark = ?, 
                update_id = ?, update_time = NOW()
            WHERE id = ?
          `;
				const [updateResult] = await connection.execute(updateSql, [configName, configKey, configValue, remark, userId, id]);
				if (updateResult.affectedRows === 0) {
					throw new Error('参数不存在');
				}
			} else {
				// 新增
				const checkSql = `SELECT id FROM sys_config WHERE config_key = ?`;
				const [checkRows] = await connection.execute(checkSql, [configKey]);
				if (checkRows.length > 0) {
					throw new Error('参数键已存在');
				}

				const insertSql = `
            INSERT INTO sys_config (config_name, config_key, config_value, remark, is_lock, create_id, create_time)
            VALUES (?, ?, ?, ?, 'F', ?, NOW())
          `;
				const [insertResult] = await connection.execute(insertSql, [configName, configKey, configValue, remark, userId]);
				id = insertResult.insertId;
			}
			return { id };
		} catch (error) {
			throw error;
		}
	}

	async deleteConfigs(ids) {
		const conn = await connection.getConnection();

		try {
			await conn.beginTransaction();

			const deleteSql = `
          DELETE FROM sys_config 
          WHERE id IN (${ids.map(() => '?').join(',')})
        `;
			const [result] = await conn.execute(deleteSql, ids);
			if (result.affectedRows === 0) {
				throw new Error('参数不存在');
			}

			await conn.commit();
			return ids;
		} catch (error) {
			await conn.rollback();
			throw error;
		} finally {
			conn.release();
		}
	}
}

module.exports = new ConfigService();
